/*

 * Copyright (C) 2021 Huawei Device Co., Ltd.

 * Licensed under the Apache License, Version 2.0 (the "License");

 * you may not use this file except in compliance with the License.

 * You may obtain a copy of the License at

 *

 *     http://www.apache.org/licenses/LICENSE-2.0

 *

 * Unless required by applicable law or agreed to in writing, software

 * distributed under the License is distributed on an "AS IS" BASIS,

 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.

 * See the License for the specific language governing permissions and

 * limitations under the License.

 */

package com.santalu.emptyview;

import ohos.agp.animation.AnimatorProperty;
import ohos.agp.components.AttrSet;
import ohos.agp.components.Component;
import ohos.agp.components.DependentLayout;
import ohos.agp.components.DirectionalLayout;
import ohos.agp.components.LayoutScatter;
import ohos.agp.components.ComponentContainer;
import ohos.agp.render.Canvas;
import ohos.app.Context;
import ohos.app.dispatcher.TaskDispatcher;
import ohos.multimodalinput.event.MmiPoint;
import ohos.multimodalinput.event.TouchEvent;

/**
 * MenuView 带弹出、收起动画的自定义菜单控件
 *
 * @author hw
 * @since 2021/5/24
 */
public class MenuView extends DependentLayout implements Component.TouchEventListener, Component.DrawTask {
    private static final long ANIMATOR_DURATION = 200;
    AnimatorProperty menuAnimatorPropertyOpen;
    AnimatorProperty menuAnimatorPropertyClose;
    private DirectionalLayout menuLayout;
    private final TaskDispatcher taskDispatcherUI;

    public MenuView(Context context) {
        this(context, null, null);
    }

    public MenuView(Context context, AttrSet attrSet) {
        this(context, attrSet, null);
    }

    public MenuView(Context context, AttrSet attrSet, String styleName) {
        super(context, attrSet, styleName);
        taskDispatcherUI = context.getUITaskDispatcher();
        Component componentMenu = LayoutScatter.getInstance(getContext())
                .parse(ResourceTable.Layout_menu_content, null, false);
        if (componentMenu instanceof DirectionalLayout) {
            menuLayout = (DirectionalLayout) componentMenu;
            LayoutConfig layoutConfig = new LayoutConfig(ComponentContainer.LayoutConfig.MATCH_CONTENT,
                    ComponentContainer.LayoutConfig.MATCH_CONTENT);
            layoutConfig.addRule(LayoutConfig.ALIGN_PARENT_TOP);
            layoutConfig.addRule(LayoutConfig.ALIGN_PARENT_RIGHT);
            menuLayout.setLayoutConfig(layoutConfig);
            addComponent(menuLayout);
        }
        addDrawTask(this);
        setTouchEventListener(this);
    }

    /**
     * 给菜单添加item
     *
     * @param child 设置单个item控件
     */
    public void setMenuItem(Component child) {
        if (child != null) {
            menuLayout.addComponent(child);
        }
    }

    @Override
    public boolean onTouchEvent(Component component, TouchEvent touchEvent) {
        MmiPoint point = touchEvent.getPointerPosition(touchEvent.getIndex());
        final float pointX = point.getX();
        final float pointY = point.getY();

        if (touchEvent.getAction() == TouchEvent.PRIMARY_POINT_DOWN
                && ((pointX < 0) || (pointX < menuLayout.getLeft())
                || (pointY < 0) || (pointY >= menuLayout.getHeight() + getPaddingTop()))) {
            dismiss(); // 碰菜单外界时关闭菜单
            return true;
        }
        return false;
    }

    /**
     * 打开菜单
     */
    public void openMenu() {
        setVisibility(VISIBLE);
        // 设置menu显示的动画
        menuAnimatorPropertyOpen.start();
    }

    /**
     * 隐藏菜单
     */
    public void dismiss() {
        menuAnimatorPropertyClose.start();
        taskDispatcherUI.delayDispatch(closeTask, 200);
    }

    private final Runnable closeTask = () -> setVisibility(HIDE);

    @Override
    public void onDraw(Component component, Canvas canvas) {
        // 初始化打开菜单动画
        menuAnimatorPropertyOpen = menuLayout
                .createAnimatorProperty()
                .moveFromX(PixelUtil.screenWidth())
                .moveToX((PixelUtil.screenWidth()) - (menuLayout.getWidth()))
                .moveFromY(-menuLayout.getHeight()).moveToY(0)
                .scaleXFrom(0).scaleX(1)
                .scaleYFrom(0).scaleY(1)
                .alphaFrom(0).alpha(1)
                .setDuration(ANIMATOR_DURATION);

        // 初始化隐藏菜单动画
        menuAnimatorPropertyClose = menuLayout
                .createAnimatorProperty()
                .setDuration(ANIMATOR_DURATION)
                .alpha(0);
    }
}
